<html>
<head><meta charset="utf-8"><title>Forced unwinding, POFs, and &quot;cancelable&quot; annotation · project-ffi-unwind · Zulip Chat Archive</title></head>
<h2>Stream: <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/index.html">project-ffi-unwind</a></h2>
<h3>Topic: <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html">Forced unwinding, POFs, and &quot;cancelable&quot; annotation</a></h3>

<hr>

<base href="https://rust-lang.zulipchat.com">

<head><link href="https://rust-lang.github.io/zulip_archive/style.css" rel="stylesheet"></head>

<a name="205746321"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/205746321" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BatmanAoD (Kyle Strand) <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#205746321">(Aug 02 2020 at 22:15)</a>:</h4>
<p>I know Niko wanted the group to take a break from doing spec-work for a bit, but I do want to start thinking about what the requirements are for making <code>longjmp</code> &amp;co well defined.</p>
<p>We already have some thoughts about what a specification will eventually look like:</p>
<ul>
<li>We should define the behavior in terms of the language features involved so that we do not have different guarantees for different targets. In other words, <code>longjmp</code> on Windows shouldn't have a different specification just because it uses unwinding as an implementation detail.<ul>
<li>I do <em>not</em> think that it is a requirement to specify that the behavior will be exactly the same on all platforms; in particular, I suspect that WIndows' use of SEH will enable optimizations around <code>longjmp</code> that would be unsafe on other platforms.</li>
</ul>
</li>
<li>We should define all "<code>longjmp</code>-like" behavior, i.e. behavior that can be implemented via forced unwinding, in the same way. (I.e. there should be no difference between <code>pthread_cancel</code> traversing a POF versus <code>longjmp</code> traversing a POF.)</li>
<li>We will require POFs for any safe <code>longjmp</code> behavior. (This is already specified by the RFC we merged.)</li>
<li>We think it would be valuable to require an annotation in order to make <code>longjmp</code> well-defined. We do not have a name for this annotation yet, but it will be linked to the concept of "<code>longjmp</code>-like" behavior. One of the terms we've been using to refer to this annotation is "cancelable". Reasons for the annotation are:<ul>
<li>semantic tractability of <code>longjmp</code>-reliant code (functions that may not return "normally" would be required to be annotated)</li>
<li>optimization potential (I will find our prior discussions on this point and link them... eventually)</li>
<li>enables better compiler warnings and errors, e.g. for ensuring that "cancelable" frames are in fact POFs</li>
</ul>
</li>
</ul>
<p>The only hard requirements I'm aware of are:</p>
<ul>
<li>There must be a sound way to call <code>libc</code> functions that may be terminated by <code>pthread_cancel</code>.</li>
<li>There must be a sound way for libraries like <code>rlua</code> to <code>longjmp</code> over Rust frames.</li>
</ul>



<a name="205836834"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/205836834" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> Amanieu <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#205836834">(Aug 03 2020 at 19:27)</a>:</h4>
<p>I don't think supporting <code>pthread_cancel</code> is a hard requirement. We could just say that <code>pthread_cancel</code> is UB if canceling a thread that has a Rust frame on the stack.</p>



<a name="205840617"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/205840617" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BatmanAoD (Kyle Strand) <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#205840617">(Aug 03 2020 at 20:01)</a>:</h4>
<p>I thought that was the primary reason we have UB in <code>libc</code> calls?</p>



<a name="205844530"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/205844530" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> Amanieu <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#205844530">(Aug 03 2020 at 20:37)</a>:</h4>
<p>We can just punt the safety responsibility to the caller of <code>pthread_cancel</code> (which is FFI an therefore <code>unsafe</code>).</p>



<a name="205844796"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/205844796" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BatmanAoD (Kyle Strand) <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#205844796">(Aug 03 2020 at 20:39)</a>:</h4>
<p>But if it's UB to have Rust on the stack <em>at all</em>, there's no way to actually uphold that responsibility...right?</p>



<a name="206043920"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206043920" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BatmanAoD (Kyle Strand) <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206043920">(Aug 05 2020 at 16:23)</a>:</h4>
<p><span class="user-mention" data-user-id="120791">@RalfJ</span> Is calling <code>libc</code> functions that may <code>pthread_cancel</code> one of the soundness issues you are concerned about? I thought it was the primary one.</p>



<a name="206046970"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206046970" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> RalfJ <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206046970">(Aug 05 2020 at 16:46)</a>:</h4>
<p>pthread_cancel is definitely on the "horribly unsound" list of things</p>



<a name="206047038"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206047038" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> RalfJ <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206047038">(Aug 05 2020 at 16:47)</a>:</h4>
<p>I dont think I have a <em>primary</em> soundness concern about unwinding, I just dont know enough about it. I dont have a big-picture view. I just know some bits and pieces.</p>



<a name="206056729"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206056729" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> bjorn3 <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206056729">(Aug 05 2020 at 18:00)</a>:</h4>
<p>Can we make the personality function abort on forced unwinds? That would solve the whole unsoundness on systems using DWARF unwinding. It should also be possible to detect POF's from the personality function if you only want to abort for non-POF's.</p>



<a name="206063638"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206063638" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BatmanAoD (Kyle Strand) <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206063638">(Aug 05 2020 at 18:54)</a>:</h4>
<p>See my first post:  we don't want to specify different behavior for the same language feature depending on what implementation the platform uses. <code>longjmp</code> should either work if the code is correct, or not.</p>



<a name="206064767"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206064767" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> bjorn3 <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206064767">(Aug 05 2020 at 19:04)</a>:</h4>
<p><code>longjmp</code> doesn't use forced unwindings on platforms using DWARF unwinding, only on Windows with SEH, right?</p>



<a name="206064852"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206064852" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BatmanAoD (Kyle Strand) <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206064852">(Aug 05 2020 at 19:05)</a>:</h4>
<p>Correct. Sorry, I didn't just mean <code>longjmp</code>; I also mean <code>pthread_exit</code>.</p>



<a name="206066060"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206066060" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> bjorn3 <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206066060">(Aug 05 2020 at 19:16)</a>:</h4>
<p>Windows doesn't have <code>pthread_exit</code>, right?</p>



<a name="206066303"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206066303" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BatmanAoD (Kyle Strand) <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206066303">(Aug 05 2020 at 19:19)</a>:</h4>
<p>I suspect that it exists as part of MinGW, but no, native MSVC-based runtimes shouldn't.</p>



<a name="206212467"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206212467" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> Peter Rabbit <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206212467">(Aug 07 2020 at 00:14)</a>:</h4>
<p><span class="user-mention silent" data-user-id="133247">bjorn3</span> <a href="#narrow/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation/near/206066060">said</a>:</p>
<blockquote>
<p>Windows doesn't have <code>pthread_exit</code>, right?</p>
</blockquote>
<p>It has <code>ExitThread</code> which as far as I can tell does roughly the same thing that <code>pthread_exit</code> does.</p>



<a name="206233373"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206233373" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> bjorn3 <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206233373">(Aug 07 2020 at 08:17)</a>:</h4>
<p>Does Windows have a way to detect this kind of forced unwinding and abort when it happens, but not abort on longjmp?</p>



<a name="206265308"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206265308" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> Peter Rabbit <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206265308">(Aug 07 2020 at 14:43)</a>:</h4>
<p>It's not really unwinding. The thread just terminates, the stack is deallocated, any pending IO is cancelled, and anything with destructors is totally leaked.</p>



<a name="206308975"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/210922-project-ffi-unwind/topic/Forced%20unwinding%2C%20POFs%2C%20and%20%22cancelable%22%20annotation/near/206308975" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BatmanAoD (Kyle Strand) <a href="https://rust-lang.github.io/zulip_archive/stream/210922-project-ffi-unwind/topic/Forced.20unwinding.2C.20POFs.2C.20and.20.22cancelable.22.20annotation.html#206308975">(Aug 07 2020 at 21:01)</a>:</h4>
<p>My primary point about the cross-platform differences is that from the perspective of Rust's (currently informal) specification, the language features in question (thread termination and <code>longjmp</code>) should not be specified differently depending on the target platform's implementation of the feature.</p>
<p>In other words, the user should not need to know whether such features are implemented with forced unwinding or simple stack deallocation.</p>



<hr><p>Last updated: Aug 07 2021 at 22:04 UTC</p>
</html>